package Data;

import java.io.Serializable;
import java.util.List;

public class FAT implements Serializable {

    private DiskBlock[] diskBlocks; //磁盘块
    private File root; //根文件

    public FAT(){
        diskBlocks = new DiskBlock[128];
        diskBlocks[0] = new DiskBlock(0,-1,"系统文件",null);
        diskBlocks[1] = new DiskBlock(1,-1,"系统文件",null);
        for(int i = 2; i < 128; i++){
            diskBlocks[i] = new DiskBlock(i,0,null,null);
        }

    }

    public DiskBlock[] getDiskBlocks() {
        return diskBlocks;
    }

    //判断空间是否足够
    public boolean judge(File file){
        int sum = 0;
        for(int i = 2; i < 128; i++){
            if(diskBlocks[i].getNextDiskNum() == 0){
                sum++;
            }
        }
       int needNum = file.getNeed();
        System.out.println("needNum:" + needNum);
        if(needNum <= sum){
            return true;
        }else {
            return false;
        }
    }
    public void applySpace(File file){
        int neededDiskNum = file.getLength();
        int record = neededDiskNum ;
        int previous = 0;
        String fileType = "";
        if(file.isFolder){
            fileType = "文件夹";
        }else {
            fileType = "普通文件";
        }
        if(file.getDiskStartNum() == 0){
            for(int i = 0; i < 128; i++){
                if(record > 1) {
                    if (diskBlocks[i].getNextDiskNum() == 0) {
                        if(record != neededDiskNum){
                            diskBlocks[previous].setNextDiskNum(i);
                        }
                        if(record == neededDiskNum){
                            file.setDiskStartNum(i);
                        }
                        diskBlocks[i].setFile(file);
                        diskBlocks[i].setType(fileType);
                        diskBlocks[i].allowNextBlock();
                        record--;
                    }
                }else {
                    if(diskBlocks[i].getNextDiskNum() == 0){
                        file.setDiskStartNum(i);
                        diskBlocks[i].setNextDiskNum(-1);
                        diskBlocks[i].setType(fileType);
                        diskBlocks[i].setFile(file);
                        diskBlocks[i].allowNextBlock();
                        break;
                    }
                }
            }
        }else {
            int sum = 1;
            previous = file.getDiskStartNum();
            while(diskBlocks[previous].getNextDiskNum() != -1){
                sum++;
                previous = diskBlocks[previous].getNextDiskNum();
            }
            if(sum == neededDiskNum){
               return;
            }
            if(sum < neededDiskNum){
                int need = neededDiskNum - sum;
                int t = previous;
                for(int i = 2; i < 128; i++){
                    if(diskBlocks[i].getNextDiskNum() == 0){
                        diskBlocks[t].setNextDiskNum(i);
                        t = i;
                        diskBlocks[i].setType(fileType);
                        diskBlocks[i].setFile(file);
                        diskBlocks[i].allowNextBlock();
                        need--;
                    }
                    if(need == 0){
                        diskBlocks[i].setNextDiskNum(-1);
                        diskBlocks[i].allowNextBlock();
                        break;
                    }
                }
            }
            if(sum > neededDiskNum){
                int t = 0,t2;
                previous = file.getDiskStartNum();
                int t1 = previous;
                while(diskBlocks[t1].getNextDiskNum() != -1){
                    t++;
                    t2 = diskBlocks[t1].getNextDiskNum();
                    if(t == neededDiskNum){
                        diskBlocks[t1].setNextDiskNum(-1);
                    }
                    if(t > neededDiskNum){
                        diskBlocks[t1].setNextDiskNum(0);
                        diskBlocks[t1].setFile(null);
                        diskBlocks[t1].setType(null);
                        diskBlocks[t1].clearBlock();
                    }
                    t1 = t2;
                }
                diskBlocks[t1].setNextDiskNum(0);
                diskBlocks[t1].setFile(null);
                diskBlocks[t1].setType(null);
                diskBlocks[t1].clearBlock();
            }
        }
    }

    public void reclaimSpace(File file){
        int startNum = file.getDiskStartNum();
        int t = startNum;
        int record = t;
        while(t != -1){
            diskBlocks[t].setFile(null);
            diskBlocks[t].setType(null);
            record = diskBlocks[t].getNextDiskNum();
            diskBlocks[t].setNumber(0);
            diskBlocks[t].clearBlock();
            t = record;
        }
    }

    public void setDiskBlocks(DiskBlock[] diskBlocks) {
        this.diskBlocks = diskBlocks;
    }

    public File getRoot() {
        return root;
    }

    public void setRoot(File root) {
        this.root = root;
    }




}
